#include "files_io.h"

#include <cassert>
#include <fstream>
#include <boost/filesystem.hpp>
#include <boost/algorithm/string.hpp>

namespace tools
{

str_t get_file_name_from_path(const str_t &file_path)
{
    return file_path.substr(file_path.rfind('/') + 1,
                            file_path.rfind('.') - file_path.rfind('/') - 1);
}

str_t get_file_format_from_path(const str_t &file_path)
{
    return file_path.substr(file_path.rfind('.') + 1);
}

/////////////////////////////////////////////////////////////////////////////////////////////////////////////////
/**
 * @brie: 获取目录 'root_dir' 下所有文件的路径，忽略文件夹
 */
void get_dir_file_paths(const str_t &_root_dir, s_vec_t &file_paths)
{
    boost::filesystem::path root_dir(_root_dir);
    boost::filesystem::directory_iterator endIter;
    for (boost::filesystem::directory_iterator iter(root_dir); iter != endIter; iter++)
    {
        if (boost::filesystem::is_regular_file(*iter))
        {
            file_paths.push_back(iter->path().string());
        }
    }
}

void get_dir_directorise(const str_t &root_dir, s_vec_t &directories)
{
    assert(boost::filesystem::exists(root_dir));
    assert(boost::filesystem::is_directory(root_dir));

    boost::filesystem::directory_iterator iter(root_dir);
    boost::filesystem::directory_iterator iter_end;

    for (; iter != iter_end; iter++)
    {
        if (boost::filesystem::is_directory(*iter))
        {
            directories.push_back(iter->path().string());
        }
    }
}

/////////////////////////////////////////////////////////////////////////////////////////////////////////////////
/**
 * @brie: 读取训 txt 文件的内容，并且将其内容按行存放在数组中
 */
void read_txt_file(const str_t &file_path, s_vec_t &file_contents)
{
    std::ifstream infile;
    infile.open(file_path.data());
    assert(infile.is_open());

    // 逐行读取文件内容，保存到vector 容器中
    std::string s;
    while (std::getline(infile, s))
    {
        file_contents.push_back(s);
    }
    infile.close();
}

/////////////////////////////////////////////////////////////////////////////////////////////////////////////////
void extract_info_from_str_line(const str_t &str_line, i_vec_t &nums, s_vec_t &strs, const str_t &spacer)
{
    std::vector<std::string> vec_str;
    boost::split(vec_str, str_line, boost::is_any_of(spacer));

    for_each(vec_str.begin(), vec_str.end(),
             [&nums, &strs](const std::string &curr_str) -> void {
                 try
                 {
                     nums.push_back(std::stof(curr_str) + 0.5);
                 }
                 catch (std::invalid_argument e)
                 {
                     strs.push_back(curr_str);
                 }
             });
}

/////////////////////////////////////////////////////////////////////////////////////////////////////////////////
void extract_info_from_txt_file(const std::string &label_txt_file_path,
                                indexes_container_t &indexes,
                                s_vec_t &labels)
{
    std::vector<std::string> content_lines;
    read_txt_file(label_txt_file_path, content_lines);
    for_each(content_lines.begin(), content_lines.end(),
             [&indexes, &labels](const std::string &curr_line) -> void {
                 i_vec_t index;
                 s_vec_t label;
                 extract_info_from_str_line(curr_line, index, label, " ");
                 if (!index.empty())
                 {
                     index.pop_back(); // 舍弃末尾 0
                     indexes.push_back(index);
                     labels.push_back(label[0]);
                 }
             });
}

void save_txt_file(const str_t &file_path, s_vec_t &file_contents)
{
    ;
}
}